/**
 * @author  weigao<weigao@iflytek.com>
 *
 * @version 1.0.0
 */
package com.iflytek.uoamp.agent.monitor.dump;

import com.iflytek.uoamp.agent.common.util.WFile;
import com.iflytek.uoamp.agent.monitor.dump.PSInfoCache.PSInfo;
import com.iflytek.uoamp.agent.monitor.dump.obj.DumpTask;
import com.iflytek.uoamp.agent.monitor.dump.obj.FileUpload;
import com.iflytek.uoamp.agent.monitor.find.CMDExextor;

import org.apache.log4j.Logger;

import java.text.SimpleDateFormat;
import java.util.Date;

public class Dumper extends Thread{
	
	private DumpTask task = null;
	private PSInfo info = null;
	private SimpleDateFormat format = new SimpleDateFormat("yyyyMMddHHmm");
	private String path = null;
	private String fileName = null;


	/***
	 * 获取文件的名称；不包含路径
	 * @return
	 */
	private String getFileName(){
		if(fileName!=null){
			return fileName;
		}
		StringBuilder sb = new StringBuilder();
		if("jstack".equals(task.getRun_command())){
			sb.append(task.getDisplay_name());
			sb.append("_");
			sb.append(format.format(new Date()));
			sb.append(".jstack");
		}else if("jmap".equals(task.getRun_command())){
			sb.append(task.getDisplay_name());
			sb.append("_");
			sb.append(format.format(new Date()));
			sb.append(".jmap");
		}
		fileName = sb.toString();
		return fileName;
	}

	/**
	 * 拼接文件的路径；如果文件路径生成过；则直接返回；
	 * @return
	 */
	private String getFullPath(){
		if(path!=null){
			return path;
		}
		StringBuilder sb = new StringBuilder();
		sb.append("temp/");
		sb.append(getFileName());
		path = sb.toString();
		return path;
	}
	
	public Dumper(PSInfo info,DumpTask task){
		this.task = task;
		this.info = info;
	}
	
	/**
	 * 获取任务的状态信息
	 * @return
	 */
	public DumpTask getTaskInfo(){
		return task;
	}
	
	/**
	 * 获取dump命令；支持jstack和jmap两种形式
	 * jstack的格式为：
	 * jstack <pid> > temp/<monitor_name>_<time>.jstack
	 * jmap的格式为：
	 * jmap -dump:format=b,file=temp/<monitor_name>_<time>.jmap <pid>
	 * @return
	 */
	private String getRunCmd(){
		StringBuilder sb = new StringBuilder();
		if("jstack".equals(task.getRun_command())){
			sb.append("jstack -F ");
			sb.append(info.getPid());
		}else if("jmap".equals(task.getRun_command())){
			sb.append("jmap -dump:format=b,file=");
			sb.append(getFullPath());
			sb.append(" ");
			sb.append(info.getPid());
		}
		return sb.toString();
	}
	
	/**
	 * 压缩文件；
	 * @return
	 */
	private String getTarCmd(){
		StringBuilder sb = new StringBuilder();
		sb.append("cmd/linux/runtar.sh ");
		sb.append(getFullPath());
		sb.append(".tar ");
		sb.append(getFullPath());
		return sb.toString();
	}
	
	
	/**
	 * 执行dump操作；
	 * 操作过程如下：
	 * 1、执行dump命令
	 * 2、压缩dump文件
	 * 3、上传dump压缩文件到mcserver
	 * 4、设置下次的运行时间（依据dump间隔）
	 * 5、删除dump文件
	 */
	@Override
	public void run() {
		Logger.getRootLogger().info("INFO|start task "+task);
		task.setFinsh_stat(DumpTaskGetter.DUMP_FINISH_READY);
		CMDExextor.ShellResult execut = CMDExextor.execut(getRunCmd());
		if("jstack".equals(task.getRun_command())){
			WFile.wf(getFullPath(), execut.output, "utf-8", false);
		}
		Logger.getRootLogger().info("INFO|dump finish and start tar "+task);
		task.setFinsh_stat(DumpTaskGetter.DUMP_FINISH_DUMPFINISH);
		CMDExextor.execut(getTarCmd());
		task.setFinsh_stat(DumpTaskGetter.DUMP_FINISH_UPDATEING);
		Logger.getRootLogger().info("INFO|tar finish and start upload " + task);
		int isFinish = new FileUpload(fileName+".tar",getFullPath()+".tar").doUpload();
		if(isFinish == FileUpload.LOAD_FINISH){
			task.setFinsh_stat(DumpTaskGetter.DUMP_FINISH_FINISH);
			Logger.getRootLogger().info("INFO|upload success " + task);
		}else{
			task.setFinsh_stat(DumpTaskGetter.DUMP_UPLOAD_ERROR);
			Logger.getRootLogger().info("INFO|upload error " + task);
		}

		if(task.getTask_type()!=DumpTaskGetter.DUMP_TASK_TYPE_NOW && task.getTask_type()!=DumpTaskGetter.DUMP_TASK_TYPE_ONLYONE) {
			task.setNextRunTime();
		}
		//删除原始文件
		CMDExextor.execut("rm -rf " + getFullPath());
		CMDExextor.execut("rm -rf " + getFullPath() + ".tar");
	}
	
}
